
#include <stdio.h>
#include <stdlib.h>
#include <engine.h>
#include <SDL.h>
#include <GL/glew.h>
#include <CEGUI.h>
#include <CEGUIDefaultResourceProvider.h>
#include <RendererModules/OpenGL/CEGUIOpenGLRenderer.h>

#ifdef __WIN32__
#include <windows.h>
#endif


void handle_mouse_down(Uint8 button)
{
  switch ( button )
    {
    // handle real mouse buttons
    case SDL_BUTTON_LEFT:
      CEGUI::System::getSingleton().injectMouseButtonDown(CEGUI::LeftButton);
      break;
    case SDL_BUTTON_MIDDLE:
      CEGUI::System::getSingleton().injectMouseButtonDown(CEGUI::MiddleButton);
      break;
    case SDL_BUTTON_RIGHT:
      CEGUI::System::getSingleton().injectMouseButtonDown(CEGUI::RightButton);
      break;

    // handle the mouse wheel
    case SDL_BUTTON_WHEELDOWN:
      CEGUI::System::getSingleton().injectMouseWheelChange( -1 );
      break;
    case SDL_BUTTON_WHEELUP:
      CEGUI::System::getSingleton().injectMouseWheelChange( +1 );
      break;
    }
}

void handle_mouse_up(Uint8 button)
{
  switch ( button )
    {
    case SDL_BUTTON_LEFT:
      CEGUI::System::getSingleton().injectMouseButtonUp(CEGUI::LeftButton);
      break;
    case SDL_BUTTON_MIDDLE:
      CEGUI::System::getSingleton().injectMouseButtonUp(CEGUI::MiddleButton);
      break;
    case SDL_BUTTON_RIGHT:
      CEGUI::System::getSingleton().injectMouseButtonUp(CEGUI::RightButton);
      break;
    }
}


void inject_time_pulse(double& last_time_pulse)
{
  /* get current "run-time" in seconds */
  double t = 0.001*SDL_GetTicks();
  /* inject the time that passed since the last call */
  CEGUI::System::getSingleton().injectTimePulse( float(t-last_time_pulse) );
  /* store the new time as the last time */
  last_time_pulse = t;
}

void init_gui ()
{

}

#ifdef __WIN32__
int WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
#else
int main (int, char**)
#endif
{
  SDL_Init(SDL_INIT_VIDEO | SDL_INIT_NOPARACHUTE);

  vgl::Engine engine;

  vgl::Engine::Config config;
  memset(&config, 0, sizeof(vgl::Engine::Config));
  config.windowCreate = true;
  config.windowWidth = 1024;
  config.windowHeight = 768;
  config.windowFullscreen = false;

  if (!engine.Initialize(config))
    {
      printf ("Unable to configure engine\n");
      return -1;
    }

  vgl::gfx::gl20::Device* device = engine.GetDevice();

  bool running = true;


  CEGUI::OpenGLRenderer& ceRenderer = CEGUI::OpenGLRenderer::create(CEGUI::Size (config.windowWidth, config.windowHeight));
  CEGUI::System::create(ceRenderer);


  CEGUI::WindowManager& winMgr = CEGUI::WindowManager::getSingleton();
  CEGUI::Window* rootWindow = winMgr.createWindow("DefaultWindow", "root");
  CEGUI::System::getSingleton().setGUISheet(rootWindow);

  CEGUI::DefaultResourceProvider* rp = (CEGUI::DefaultResourceProvider*)CEGUI::System::getSingleton().getResourceProvider();
  rp->setResourceGroupDirectory ("gui", "../../trunk/media/gui/");

  CEGUI::Imageset::setDefaultResourceGroup("gui");
  CEGUI::Scheme::setDefaultResourceGroup("gui");
  CEGUI::WindowManager::setDefaultResourceGroup("gui");
  CEGUI::WidgetLookManager::setDefaultResourceGroup("gui");
  CEGUI::Font::setDefaultResourceGroup("gui");

  CEGUI::SchemeManager::getSingleton().create ("TaharezLook.scheme");

  CEGUI::Window* textWnd = winMgr.createWindow("TaharezLook/StaticText", "StaticText");
  textWnd->setText("This is my Text");
  textWnd->setWidth(CEGUI::UDim(1.0f, 0));
  textWnd->setHeight(CEGUI::UDim(0.05f, 0));
  textWnd->setHorizontalAlignment(CEGUI::HA_RIGHT);
  textWnd->update(0);
  rootWindow->addChildWindow(textWnd);

  CEGUI::FrameWindow* fWnd = (CEGUI::FrameWindow*)winMgr.createWindow("TaharezLook/FrameWindow", "testWindow");
  rootWindow->addChildWindow(fWnd);

  fWnd->setPosition(CEGUI::UVector2(CEGUI::UDim(0.25f, 0), CEGUI::UDim(0.25f, 0)));
  fWnd->setSize(CEGUI::UVector2(CEGUI::UDim(0.5f, 0), CEGUI::UDim(0.5f, 0)));
  fWnd->setText("Hello World!");

  fWnd = (CEGUI::FrameWindow*)winMgr.createWindow("TaharezLook/FrameWindow", "testWindow2");
  rootWindow->addChildWindow(fWnd);


  fWnd->setPosition(CEGUI::UVector2(CEGUI::UDim(0.75f, 0), CEGUI::UDim(0.75f, 0)));
  fWnd->setSize(CEGUI::UVector2(CEGUI::UDim(0.5f, 0), CEGUI::UDim(0.5f, 0)));
  fWnd->setText("Hello World 1");

  double last_time_pulse = 0.001*static_cast<double>(SDL_GetTicks());

  while (running)
    {
      SDL_Event e;
      while (SDL_PollEvent(&e))
        {
          switch (e.type)
              {
                // mouse motion handler
                case SDL_MOUSEMOTION:
                  // we inject the mouse position directly.
                  CEGUI::System::getSingleton().injectMousePosition(
                    static_cast<float>(e.motion.x),
                    static_cast<float>(e.motion.y)
                  );
                  break;

                // mouse down handler
                case SDL_MOUSEBUTTONDOWN:
                  // let a special function handle the mouse button down event
                  handle_mouse_down(e.button.button);
                  break;

                // mouse up handler
                case SDL_MOUSEBUTTONUP:
                  // let a special function handle the mouse button up event
                  handle_mouse_up(e.button.button);
                  break;


                // key down
                case SDL_KEYDOWN:
                  // to tell CEGUI that a key was pressed, we inject the scancode.
                  CEGUI::System::getSingleton().injectKeyDown(e.key.keysym.scancode);

                  // as for the character it's a litte more complicated. we'll use for translated unicode value.
                  // this is described in more detail below.
                  if (e.key.keysym.unicode != 0)
                  {
                    CEGUI::System::getSingleton().injectChar(e.key.keysym.unicode);
                  }
                  break;

                // key up
                case SDL_KEYUP:
                  if (e.key.keysym.sym == SDLK_ESCAPE)
                    {
                      running = false;
                    }
                  // like before we inject the scancode directly.
                  CEGUI::System::getSingleton().injectKeyUp(e.key.keysym.scancode);
                  break;


                // WM quit event occured
                case SDL_QUIT:
                  running = false;
                  break;

              }
        }
      glClearColor (0.0f, 0.0f, 0.2f, 1.0f);
      glClear (GL_COLOR_BUFFER_BIT);
      inject_time_pulse(last_time_pulse);
      CEGUI::System::getSingleton().renderGUI();
      SDL_GL_SwapBuffers();
    }
  SDL_ShowCursor(1);
  SDL_Quit();

  return 0;
}
